package log

import (
	"fmt"
	"go.uber.org/zap"
	"go.uber.org/zap/zapcore"
	"os"
	"runtime"
	"sync"
)

var (
	logger *zap.SugaredLogger
	once   sync.Once
)

func Logger() *zap.SugaredLogger {
	once.Do(func() {
		encoderConfig := zapcore.EncoderConfig{
			TimeKey:        "time",
			LevelKey:       "level",
			MessageKey:     "msg",
			EncodeTime:     zapcore.RFC3339TimeEncoder,
			EncodeLevel:    zapcore.CapitalColorLevelEncoder,
			EncodeCaller:   zapcore.ShortCallerEncoder,
			EncodeDuration: zapcore.SecondsDurationEncoder,
		}
		//config := zap.Config{
		//	Level:       zap.NewAtomicLevelAt(zap.DebugLevel),
		//	Development: false,
		//	Encoding:    "json",
		//	EncoderConfig: encoderConfig,
		//	OutputPaths:      []string{"stdout"},
		//	ErrorOutputPaths: []string{"stderr"},
		//}

		consoleEncoder := zapcore.NewConsoleEncoder(encoderConfig)
		core := zapcore.NewCore(
			consoleEncoder,
			zapcore.Lock(zapcore.AddSync(zapcore.Lock(os.Stdout))),
			zap.NewAtomicLevelAt(zapcore.DebugLevel),
		)

		z := zap.New(core)
		logger = z.Sugar()
	})
	return logger
}

// Info 记录信息日志，并添加调用者信息
func Info(args ...interface{}) {
	l := Logger()
	// 获取调用者信息
	//_, file, line, ok := runtime.Caller(1)
	//if ok {
	//	l = l.With("caller", file+":"+string(line))
	//}
	l.Info(args...)
}

// Warn 记录警告日志，并添加调用者信息
func Warn(args ...interface{}) {
	l := Logger()
	// 获取调用者信息
	//_, file, line, ok := runtime.Caller(1)
	//if ok {
	//	l = l.With("caller", file+":"+string(line))
	//}
	l.Warn(args)
}

// Error 记录错误日志，并添加调用者信息
func Error(err error, args ...interface{}) error {
	var caller string
	//var log *zap.SugaredLogger
	l := Logger()
	// 获取调用者信息
	_, file, line, ok := runtime.Caller(1)
	if ok {
		caller = fmt.Sprintf("%s:%d", file, line)
		l = l.With("caller", caller)
	}
	l.Error(err.Error(), args)
	return err
}

func Debug(msg string, args ...interface{}) {
	//var caller string
	l := Logger()
	// 获取调用者信息
	//_, file, line, ok := runtime.Caller(1)
	//if ok {
	//	caller = fmt.Sprintf("%s:%d", file, line)
	//	l = l.With("caller", caller)
	//}
	l.Debug(msg, args)
}

// Error 记录错误日志，并添加调用者信息
func Debugf(template string, args ...interface{}) {
	l := Logger()
	// 获取调用者信息
	//_, file, line, ok := runtime.Caller(1)
	//if ok {
	//	l = l.With("caller", file+":"+string(line))
	//}
	l.Debugf(template, args)
}
